/**
 * 创建request请求
 * @returns
 */

import config from '@/utils/config'
import store from '@/store'
let appVersion = uni.getSystemInfoSync().appVersion
let osName = uni.getSystemInfoSync().osName
if(uni.getSystemInfoSync().uniPlatform=='mp-weixin'){
	osName = 'miniapp'
}

// 请求白名单，无须token的接口
const whiteList: string[] = ['/member/auth/send-sms-code', '/member/auth/sms-login','/member/app-config/index-config/1','/member/app-config/index-config/2','/member/app-config/index-config/3','/member/app-config/index-config/4','/rooms/apartment/guess-list','/rooms/home/search-room','/member/auth/phone-login','/member/auth/refresh-token','/member/auth/get-phone-code','/member/wx-mp/code2session','/member/wx-mp/get-phone']

const request = <T = any>(
	url: string,
	type: 'OPTIONS' | 'GET' | 'HEAD' | 'POST' | 'PUT' | 'DELETE' | 'TRACE' | 'CONNECT', //请求方式
	data: AnyObject, //请求的参数
	header: any //设置请求的 header
): Promise<T> => {
	// 拼接url  config.base后面会讲到
    let apiUrl = config.baseUrl + url
  // 全局添加请求头
	let obj = {
		// 获取Store中的token || 获取本地存储的token
		'Authorization': whiteList.indexOf(url) === -1?(store.state.accessToken || uni.getStorageSync('accessToken') || ""):'',
		'Tenant-Id': uni.getStorageSync('tenantId'),
		'AppVersion': `${osName}/${appVersion}`
	}
	if (header) {
		// 有无传入header，有则合并
		let headers = Object.assign(header, obj);
		header = headers;
	} else {
		header = obj
	}
	if (data) {
		// 清除无用参数
		Object.keys(data).forEach(key => {
			if (data[key] == null || data[key] == undefined) {
				delete (data[key]);
			}
		})
	}
 
	return new Promise((resolve, reject) => {
		uni.request({
		    url: apiUrl,
		    method: type,
		    data,
		    header,
		    success(res) {
				if (res.statusCode == 200) {
					const data: any = res.data;
					if (data.code == 0) {
						// 正常抛出数据
						resolve(data.data as T)
					} else {
						if(data.code == 401) {
							let pages = getCurrentPages();
							let curPage = pages.length?pages[pages.length-1].route:''
							console.log('curPage:'+curPage)
							store.dispatch('logOut')
							// 未登录
							if(curPage!="pages/login/login"){
								uni.navigateTo({
									url: "/pages/login/login"  //未登录跳转指定页面
								})
							}
							uni.hideLoading();
							return reject(data);
						}
						// 错误数据
						uni.hideLoading();
						// 弹窗错误框，这里是自己封装组件，
						uni.showToast({
							title: data.msg || "网络请求异常",
							icon: 'none',
						});
						reject(data);
					}
				} else if(res.statusCode == 401){
					uni.hideLoading();
					uni.showToast({
						title: "账号未登录",
						icon: 'none',
					});
					setTimeout(()=>{
						let pages = getCurrentPages();
						let curPage = pages.length?pages[pages.length-1].route:''
						console.log('curPage:'+curPage)
						store.dispatch('logOut')
						if(curPage!="pages/login/login"){
							uni.navigateTo({
								url: "/pages/login/login"  //未登录跳转指定页面
							})
						}
					},1000)
					reject(data)
				} else {
					console.log(data)
					uni.hideLoading();
					uni.showToast({
						title: "网络请求异常",
						icon: 'none',
					});
					reject(data)
				}
			},
			fail(err) {
				console.log(err)
				uni.hideLoading();
				uni.showToast({
				    title: "网络请求异常",
				    icon: 'none',
				});
				reject(err)
			}
		})
	})
}

/**
 * http get 请求
 * @param url 请求接口
 * @param data 请求参数
 * @returns
 */
const get = <T = any>(
	url: string,
	data: AnyObject
): Promise<T> => {
	return request(url, 'GET', data, {})
}
 
/**
 * http post json请求
 * @param url 请求接口
 * @param data 请求参数
 * @returns
 */
const post = <T = any>(
	url: string,
	data: AnyObject
): Promise<T> => {
	return request(url, 'POST', data, {
		'Content-Type': 'application/json'
	})
}
 
/**
 * http post form表单请求
 * @param url 请求接口
 * @param data 请求参数
 * @returns
 */
const postF = <T = any>(
	url: string,
	data: AnyObject
): Promise<T> => {
	return request(url, 'POST', data, {
		'Content-Type': 'application/x-www-form-urlencoded'
	})
}
 
/**
 * http put json请求
 * @param url 请求接口
 * @param data 请求参数
 * @returns
 */
const put = <T = any>(url: string, data: AnyObject): Promise<T> => {
	return request(url, 'PUT', data, {
		'Content-Type': 'application/json'
	})
}
 
/**
 * http put form表单请求
 * @param url 请求接口
 * @param data 请求参数
 * @returns
 */
const putF = <T = any>(url: string, data: AnyObject): Promise<T> => {
	return request(url, 'PUT', data, {
		'Content-Type': 'application/x-www-form-urlencoded'
	})
}
/**
 * http delete请求
 * @param url 请求接口
 * @param data 请求参数
 * @returns
 */
const del = <T = any>(url: string, data: AnyObject): Promise<T> => {
	return request(url, 'DELETE', data, {})
}
 
 
export default {
	get,
	post,
	postF,
	put,
	putF,
	del
}